package edu.pmfbl.mnr.sem.mcmatm.app;

import com.borland.dbswing.*;
import com.borland.dx.dataset.*;
import com.borland.dx.sql.dataset.*;
import com.borland.dx.dataset.DataModule;

import edu.pmfbl.mnr.sem.mcmatm.gui.*;

/**
 * <p>Title: MCMA Test Maker</p>
 *
 * <p>Description: </p>
 *
 * <p>Copyright: Copyright (c) 2009</p>
 *
 * <p>Company: KrndijaSoft</p>
 *
 * @author Ninoslav Krndija
 * @version 1.0
 */
public class AppDataModule implements DataModule
{
  /**
   * Data module reference.
   */
  private static AppDataModule appDataModule = null;

  /**
   * URL za konekciju na JDBC server baza podataka. Icijalizuje se preko
   * static setJDBCDataSource() metode.
   */
   static String jdbcURL;

  /**
   * Korisnicko ime za konekciju na JDBC server baza podataka. Icijalizuje se preko
   * static setJDBCDataSource() metode.
   */
   static String jdbcUser;

  /**
   * Password za konekciju na JDBC server baza podataka. Icijalizuje se preko
   * static setJDBCDataSource() metode.
   */
   static String jdbcPassword;

  /**
   * Ime drajvera za konekciju na JDBC server baza podataka. Icijalizuje se preko
   * static setJDBCDataSource() metode.
   */
   static String jdbcDriver;

   /**
    *
    */
   private static long INVALID_PITANJE = -1;

   /**
    *
    */
   private static long queryPitanje = INVALID_PITANJE;

   /**
    *
    */
   protected boolean unosenjePitanja = false;

   Database database = new Database();

   QueryDataSet pitanjaDataSet = new QueryDataSet();
   Column idColumn = new Column();
   Column nazivColumn = new Column();
   Column tekstpitanjaColumn = new Column();
   Column bodoviColumn = new Column();
   Column infoColumn = new Column();
   //QueryDataSet viseizboraDataSet = new QueryDataSet();  // INFO Obrisati
   //Column pitanjeColumn = new Column();
   Column mijesanjeodgovoraColumn = new Column();
   Column tacanodgovorinfoColumn = new Column();
   Column djelimicanodgovorinfoColumn = new Column();
   Column netacanodgovorinfoColumn = new Column();

   QueryDataSet odgovoriDataSet = new QueryDataSet();
   Column pitanje1Column = new Column();
   Column odgovorColumn = new Column();
   Column tacanColumn = new Column();
   Column info1Column = new Column();

   QueryDataSet pitanjabrDataSet = new QueryDataSet();

   DBExceptionHandler dBExceptionHandler1;

   /**
   * DataModule constructor.
   */
  public AppDataModule()
  {
    try
    {
      jbInit();
    }
    catch(Exception exception)
    {
      exception.printStackTrace();
    }
  }

  /**
   * Inicijalizacija.
   *
   * @throws java.lang.Exception
   */
  private void jbInit() throws Exception
  {
    // Eksplicitno ucitavanje klase za JDBC Driver
    Class.forName(jdbcDriver);
    database.setConnection(new com.borland.dx.sql.dataset.ConnectionDescriptor(
        jdbcURL, jdbcUser, jdbcPassword, false, ""));
    dBExceptionHandler1 = DBExceptionHandler.getInstance();

    idColumn.setColumnName("id");
    idColumn.setDataType(com.borland.dx.dataset.Variant.LONG);
    idColumn.setHidden(true);
    nazivColumn.setCaption("Naziv pitanja");
    nazivColumn.setColumnName("naziv");
    nazivColumn.setHidden(true);
    //nazivColumn.setDataType(com.borland.dx.dataset.Variant.STRING);
    nazivColumn.setRequired(true);
    tekstpitanjaColumn.setCaption("Tekst pitanja");
    tekstpitanjaColumn.setColumnName("tekstpitanja");
    //tekstpitanjaColumn.setDataType(com.borland.dx.dataset.Variant.STRING);
    tekstpitanjaColumn.setRequired(true);
    bodoviColumn.setCaption("Bodovi");
    bodoviColumn.setColumnName("bodovi");
    bodoviColumn.setDataType(com.borland.dx.dataset.Variant.LONG);
    Variant min = new Variant(com.borland.dx.dataset.Variant.LONG);
    min.setLong(1);
    bodoviColumn.setMinValue(min);
    bodoviColumn.setRequired(true);
    infoColumn.setCaption("Povratna informacija");
    infoColumn.setColumnName("info");
    //infoColumn.setDataType(com.borland.dx.dataset.Variant.STRING);
    infoColumn.setRequired(true);

    /*pitanjeColumn.setColumnName("pitanje");
    pitanjeColumn.setDataType(com.borland.dx.dataset.Variant.LONG);
    pitanjeColumn.setRequired(true);*/
    mijesanjeodgovoraColumn.setColumnName("mijesanjeodgovora");
    mijesanjeodgovoraColumn.setHidden(true);
    //mijesanjeodgovoraColumn.setRequired(true);
    tacanodgovorinfoColumn.setCaption("Povratna informacija za tačan odgovor");
    tacanodgovorinfoColumn.setColumnName("tacanodgovorinfo");
    tacanodgovorinfoColumn.setHidden(true);
    tacanodgovorinfoColumn.setRequired(true);
    djelimicanodgovorinfoColumn.setCaption("Povratna informacija za djelimično tačan odgovor");
    djelimicanodgovorinfoColumn.setColumnName("djelimicanodgovorinfo");
    djelimicanodgovorinfoColumn.setHidden(true);
    djelimicanodgovorinfoColumn.setRequired(true);
    netacanodgovorinfoColumn.setCaption("Povratna informacija za netačan odgovor");
    netacanodgovorinfoColumn.setColumnName("netacanodgovorinfo");
    netacanodgovorinfoColumn.setHidden(true);
    netacanodgovorinfoColumn.setRequired(true);

    pitanje1Column.setColumnName("pitanje");
    pitanje1Column.setDataType(com.borland.dx.dataset.Variant.LONG);
    pitanje1Column.setRequired(true);
    odgovorColumn.setCaption("Odgovor");
    odgovorColumn.setColumnName("odgovor");
    odgovorColumn.setRequired(true);
    tacanColumn.setCaption("Tačan");
    tacanColumn.setColumnName("tacan");
    info1Column.setCaption("Info");
    info1Column.setColumnName("info");
    info1Column.setRequired(true);

    /*viseizboraDataSet.setColumns(new Column[] {pitanjeColumn, mijesanjeodgovoraColumn, tacanodgovorinfoColumn,
                                 djelimicanodgovorinfoColumn, netacanodgovorinfoColumn});*/

    //pitanjaDataSet.setEnableInsert(false);
    //pitanjaDataSet.setEnableDelete(false);
    pitanjaDataSet.addEditListener(new AppDataModule_pitanjaDataSet_editAdapter(this));
    //pitanjaDataSet.addNavigationListener(new AppDataModule_pitanjaDataSet_navigationHandler(this));
    pitanjaDataSet.setQuery(new com.borland.dx.sql.dataset.QueryDescriptor(
        database, "SELECT * FROM mcma_pitanja", null, true, Load.ALL));
    pitanjaDataSet.setColumns(new Column[] {idColumn, nazivColumn, tekstpitanjaColumn, bodoviColumn, infoColumn,
        mijesanjeodgovoraColumn, tacanodgovorinfoColumn, djelimicanodgovorinfoColumn, netacanodgovorinfoColumn});
    pitanjaDataSet.executeQuery();
    //pitanjaDataSet.open();
    tekstpitanjaColumn.setPrecision(45);  // INFO izostaviti jer nedozvoljava prikaz/unos duzi od 45
    bodoviColumn.setPrecision(6);
    infoColumn.setPrecision(45);

    //odgovoriDataSet.setEnableInsert(false);
    //odgovoriDataSet.setEnableDelete(false);
    odgovoriDataSet.setMasterLink(new MasterLinkDescriptor(pitanjaDataSet,
        new String[] {"id"}, new String[] {"pitanje"}, false));
    odgovoriDataSet.setQuery(new com.borland.dx.sql.dataset.QueryDescriptor(
        database, "SELECT pitanje, odgovor, tacan, info FROM mcma_odgovori", null, true, Load.ALL));
    odgovoriDataSet.setColumns(new Column[] {pitanje1Column, odgovorColumn, tacanColumn, info1Column});
    odgovoriDataSet.executeQuery();
    odgovorColumn.setPrecision(30);
    tacanColumn.setPrecision(5);
    info1Column.setPrecision(50);

    //viseizboraDataSet.setEnableInsert(false);
    //viseizboraDataSet.setEnableDelete(false);
    //ParameterRow viseizboraDataSetQueryParameters = new ParameterRow();  // INFO 3 reda za probu umjesto MasterLink-a koriscenje parametrizovanog upita
    //viseizboraDataSetQueryParameters.addColumn("id", Variant.LONG);
    //queryPitanje = pitanjaDataSet.getLong("id");
    //viseizboraDataSetQueryParameters.setLong("id", queryPitanje);
    // umjesto MasterLink koristiti parametrizovani query
    /*viseizboraDataSet.setMasterLink(new MasterLinkDescriptor(pitanjaDataSet,
        new String[] {"id"}, new String[] {"pitanje"}, false));
    viseizboraDataSet.setQuery(new com.borland.dx.sql.dataset.QueryDescriptor(
        database, "SELECT * FROM mcma_viseizbora", null, true, Load.ALL));*/
    /*viseizboraDataSet.setQuery(new com.borland.dx.sql.dataset.QueryDescriptor(
        database, "SELECT * FROM mcma_viseizbora WHERE pitanje = :id", viseizboraDataSetQueryParameters, true, Load.ALL));*/
    /*viseizboraDataSet.setColumns(new Column[] {mijesanjeodgovoraColumn, tacanodgovorinfoColumn,
                                 djelimicanodgovorinfoColumn, netacanodgovorinfoColumn});*/
    //viseizboraDataSet.executeQuery();

    //pitanjabrDataSet.setEnableInsert(false);
    //pitanjabrDataSet.setEnableDelete(false);
    pitanjabrDataSet.setQuery(new com.borland.dx.sql.dataset.QueryDescriptor(
        database, "SELECT * FROM mcma_pitanjabr", null, false, Load.ALL));
    pitanjabrDataSet.executeQuery();

    /* Registruje DataSetExceptionHandler kao rukovaoca izuzecima tipa DataSetException
       radi prikazivanja lokalizovanih poruka */
    DataSetException.addExceptionListener(new DataSetExceptionHandler(this));
  }

  /**
   * Vraca referencu na DataModule.
   *
   * @return referenca na DataModule
   */
  public static AppDataModule getDataModule()
  {
    if(appDataModule == null)
      appDataModule = new AppDataModule();

    return appDataModule;
  }

  public static void setJDBCDataSource(String URL, String user, String password, String driver)
  {
    if(appDataModule == null)
    {
      jdbcURL = URL;
      jdbcUser = user;
      jdbcPassword = password;
      jdbcDriver = driver;
    }
  }

  public com.borland.dx.sql.dataset.QueryDataSet getPitanjaDataSet()
  {
    return pitanjaDataSet;
  }

  public com.borland.dx.sql.dataset.QueryDataSet getOdgovoriDataSet()
  {
    return odgovoriDataSet;
  }

  /*public com.borland.dx.sql.dataset.QueryDataSet getViseizboraDataSet()
  {
    return viseizboraDataSet;
  }*/

  public com.borland.dx.sql.dataset.QueryDataSet getPitanjabrDataSet()
  {
    return pitanjabrDataSet;
  }

  public boolean getUnosenjePitanja()
  {
    return unosenjePitanja;
  }

  /**
   * Inicijalizuje novo-insertovani red u pitanjaDataSet.
   *
   * @param dataSet DataSet skup podataka u koji ce biti insertovano
   * @throws DataSetException u slucaju pogresnog koriscenja DataSet-a
   */
  void pitanjaDataSet_inserted(DataSet dataSet) throws DataSetException
  {
    queryPitanje = getNextNumber(pitanjabrDataSet, "sledecepitanje");
    dataSet.setLong("id", queryPitanje);
    dataSet.setLong("bodovi", 10);
    dataSet.setBoolean("mijesanjeodgovora", true);
  }

  //void pitanjaDataSet_navigated(/*DataSet dataSet*/) throws DataSetException
  /*{
    if(!unosenjePitanja)
    {
      ParameterRow viseizboraDataSetQueryParameters = new ParameterRow(); // INFO 3 reda za probu umjesto MasterLink-a koriscenje parametrizovanog upita
      viseizboraDataSetQueryParameters.addColumn("id", Variant.LONG);
      queryPitanje = pitanjaDataSet.getLong("id");
      viseizboraDataSetQueryParameters.setLong("id", queryPitanje);
      viseizboraDataSet.close();
      viseizboraDataSet.setQuery(new com.borland.dx.sql.dataset.QueryDescriptor(
          database, "SELECT * FROM mcma_viseizbora WHERE pitanje = :id",
          viseizboraDataSetQueryParameters, true, Load.ALL));
      viseizboraDataSet.executeQuery();
      viseizboraDataSet.open();
    }
  }*/

  public void insertQuestion()
  {
    StorageDataSet dataSet = null;
    try
    {
      //pitanjaDataSet.setEnableInsert(true);
      (dataSet = pitanjaDataSet).insertRow(false);
      //pitanjaDataSet.setEnableInsert(false);

      //viseizboraDataSet.setEnableInsert(true);
      /*(dataSet = viseizboraDataSet).insertRow(false);
      (dataSet = viseizboraDataSet).setLong("pitanje", pitanjaDataSet.getLong("id"));*/
      //viseizboraDataSet.setEnableInsert(false);

      unosenjePitanja = true;
   }
    catch(DataSetException e)
    {
      dBExceptionHandler1.handleException(dataSet, null, e, true);
    }
  }

  public void deleteQuestion()
  {
    try
    {
      pitanjaDataSet.deleteRow();
      saveQuestion();
    }
    catch(DataSetException e)
    {
      dBExceptionHandler1.handleException(pitanjaDataSet, null, e, true);
    }
  }

  public void insertAnswer()
  {
    try
    {
      odgovoriDataSet.insertRow(false);
    }
    catch(DataSetException e)
    {
      dBExceptionHandler1.handleException(odgovoriDataSet, null, e, true);
    }
  }

  public boolean imaOdgovora()
  {
    return (odgovoriDataSet.getRowCount() != 0);
  }

  public boolean nemaTacnihOdgovora()
  {
    try
    {
      if(odgovoriDataSet.getRowCount() != 0)
      {
        odgovoriDataSet.first();
        while (odgovoriDataSet.inBounds())
        {
          if (odgovoriDataSet.getBoolean("tacan"))
            return false;
          odgovoriDataSet.next();
        }
      }
    }
    catch(DataSetException e)
    {
      dBExceptionHandler1.handleException(odgovoriDataSet, null, e, true);
    }
    return true;
  }

  public boolean postAnswer()
  {
    try
    {
      odgovoriDataSet.post();
      return true;
    }
    catch(DataSetException e)
    {
      dBExceptionHandler1.handleException(odgovoriDataSet, null, e, true);
    }
    return false;
  }

  public boolean saveQuestion()
  {
    StorageDataSet dataSet = null;
    try
    {
      //pitanjaDataSet.setEnableInsert(true);
      //viseizboraDataSet.setEnableInsert(true);
      //(dataSet = viseizboraDataSet).post();
      (dataSet = odgovoriDataSet).post();
      (dataSet = pitanjaDataSet).post();
      //(dataSet = pitanjabrDataSet).post();  // INFO Postovan u getNextNumber koja je ranije morala biti pozvana
      database.saveChanges(new DataSet[] {pitanjaDataSet, odgovoriDataSet, pitanjabrDataSet}, true);
      //pitanjaDataSet_navigated();
      unosenjePitanja = false;
      //pitanjaDataSet.setEnableInsert(false);
      //viseizboraDataSet.setEnableInsert(false);
      return true;
    }
    catch(DataSetException e)
    {
      dBExceptionHandler1.handleException(dataSet, null, e, true);
    }
    return false;
  }

  long getNextNumber(QueryDataSet dataSet, String columnName) throws DataSetException
  {
    dataSet.executeQuery();
    dataSet.open();
    long nextLong = dataSet.getLong(columnName);
    dataSet.setLong(columnName, nextLong + 1);
    dataSet.post();
    //dataSet.saveChanges(dataSet);
    return nextLong;
  }

  public com.borland.dbswing.DBExceptionHandler getDBExceptionHandler1()
  {
    return dBExceptionHandler1;
  }

}

class AppDataModule_pitanjaDataSet_editAdapter extends com.borland.dx.dataset.EditAdapter
{
  AppDataModule adaptee;

  AppDataModule_pitanjaDataSet_editAdapter(AppDataModule adaptee)
  {
    this.adaptee = adaptee;
  }

  public void inserted(DataSet dataSet) throws DataSetException
  {
    adaptee.pitanjaDataSet_inserted(dataSet);
  }
}

/*class AppDataModule_pitanjaDataSet_navigationHandler implements com.borland.dx.dataset.NavigationListener
{
  AppDataModule adaptee;

  AppDataModule_pitanjaDataSet_navigationHandler(AppDataModule adaptee)
  {
    this.adaptee = adaptee;
  }

  public void navigated(NavigationEvent event)
  {
    adaptee.pitanjaDataSet_navigated(/*event.getDataSet*///);
  /*}
}*/
